<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="utf-8" />
   
  <meta name="keywords" content="Java Python" />
   
  <meta name="description" content="From Zero to Hero" />
  
  <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1" />
  <title>
    SpringBoot-18-dubbo+zookeeper |  朱酱酱的学习博客
  </title>
  <meta name="generator" content="hexo-theme-yilia-plus">
  
  <link rel="shortcut icon" href="/favicon.ico" />
  
  
<link rel="stylesheet" href="/css/style.css">

  
<script src="/js/pace.min.js"></script>


  

  

<link rel="alternate" href="/atom.xml" title="朱酱酱的学习博客" type="application/atom+xml">
</head>

</html>

<body>
  <div id="app">
    <main class="content">
      <section class="outer">
  <article id="post-SpringBoot/SpringBoot-18-dubbo+zookeeper" class="article article-type-post" itemscope
  itemprop="blogPost" data-scroll-reveal>

  <div class="article-inner">
    
    <header class="article-header">
       
<h1 class="article-title sea-center" style="border-left:0" itemprop="name">
  SpringBoot-18-dubbo+zookeeper
</h1>
  

    </header>
    

    
    <div class="article-meta">
      <a href="/2020/04/06/SpringBoot/SpringBoot-18-dubbo+zookeeper/" class="article-date">
  <time datetime="2020-04-06T11:02:24.000Z" itemprop="datePublished">2020-04-06</time>
</a>
      
      
      
<div class="word_count">
    <span class="post-time">
        <span class="post-meta-item-icon">
            <i class="ri-quill-pen-line"></i>
            <span class="post-meta-item-text"> 字数统计:</span>
            <span class="post-count">4.8k字</span>
        </span>
    </span>

    <span class="post-time">
        &nbsp; | &nbsp;
        <span class="post-meta-item-icon">
            <i class="ri-book-open-line"></i>
            <span class="post-meta-item-text"> 阅读时长≈</span>
            <span class="post-count">18分钟</span>
        </span>
    </span>
</div>

      
    </div>
    

    
    
    <div class="tocbot"></div>





    

    <div class="article-entry" itemprop="articleBody">
      


      

      
      <h1 id="SpringBoot-18-dubbo-zookeeper"><a href="#SpringBoot-18-dubbo-zookeeper" class="headerlink" title="SpringBoot-18-dubbo+zookeeper"></a>SpringBoot-18-dubbo+zookeeper</h1><h2 id="1-什么是分布式系统"><a href="#1-什么是分布式系统" class="headerlink" title="1. 什么是分布式系统"></a>1. 什么是分布式系统</h2><p><strong>在《分布式系统原理与泛型》一书中有如下定义：</strong></p>
<p><strong>“分布式系统是若干独立计算机的集合，这些计算机对于用户来说就像单个相关系统”</strong></p>
<a id="more"></a>



<ul>
<li><p><strong>分布式系统是由一组通过网络进行通信，为了完成共同任务而协调工作的计算机节点组成的系统。</strong></p>
</li>
<li><p>分布式系统的出现是为了用廉价的，普通的机器完成单个计算机无法完成的计算，存储任务。其目的是利用更多的机器，处理更多的数据。</p>
</li>
<li><p>分布式系统是建立在网络之上的软件系统。</p>
</li>
</ul>
<p><strong>注意事项：</strong></p>
<ul>
<li><p>首先需要明确的是，只有当<strong>单个节点的处理能力</strong>无法满足日益增长的计算、存储任务的时候，且硬件的提升（加内存、加磁盘、使用更好的CPU）高昂到得不偿失的时候，应用程序也不能进一步优化的时候，我们<strong>才需要考虑分布式系统</strong>。</p>
</li>
<li><p>因为，<strong>分布式系统要解决的问题本身就是和单机系统一样的</strong>。</p>
</li>
<li><p>而<strong>由于分布式系统多节点、通过网络通信的拓扑结构</strong>，会引入很多单机系统没有的问题，为了解决这些问题<strong>又会引入更多的机制、协议，带来更多的问题</strong>。</p>
</li>
</ul>
<h2 id="2-系统架构的演进"><a href="#2-系统架构的演进" class="headerlink" title="2. 系统架构的演进"></a>2. 系统架构的演进</h2><h3 id="2-1-单体应用架构（All-in-one）"><a href="#2-1-单体应用架构（All-in-one）" class="headerlink" title="2.1 单体应用架构（All in one）"></a>2.1 单体应用架构（All in one）</h3><ul>
<li>当网站流量很小时，<strong>只需要一个应用，就能将所有的功能都部署在一起，</strong>以减少部署节点和成本。此时，用于简化增加改查的<strong>数据访问架构（ORM）</strong>是关键。</li>
</ul>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410110006.png" alt=""></p>
<p>适用于小型网站，小型管理系统，将所有功能都部署到一个功能里，简单易用。</p>
<p><strong>缺点：</strong></p>
<p>1、性能扩展比较难</p>
<p>2、协同开发问题</p>
<p>3、不利于升级维护</p>
<h3 id="2-2-垂直应用架构-MVC"><a href="#2-2-垂直应用架构-MVC" class="headerlink" title="2.2 垂直应用架构 (MVC)"></a>2.2 垂直应用架构 (MVC)</h3><ul>
<li>当网站访问量逐渐增大，单一应用增加机器带来的加速度越来越小，将应用拆分成互不相干的几个应用，以提升效率。此时，<strong>用于加速前端页面开发的Web框架（MVC）是关键。</strong></li>
</ul>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410110339.png" alt=""></p>
<p>优点：</p>
<ul>
<li>系统拆分实现了流量的分单</li>
<li>可以针对不同的横块进行优化</li>
<li>方便横向扩展，负载均衡，容错率提高</li>
</ul>
<p>缺点：</p>
<ul>
<li>系统之间相互独立，<strong>会出现很多的重复开发</strong>，影响开发的效率</li>
</ul>
<h3 id="2-3-分布式服务架构-RPC"><a href="#2-3-分布式服务架构-RPC" class="headerlink" title="2.3 分布式服务架构(RPC)"></a>2.3 分布式服务架构(RPC)</h3><ul>
<li>当垂直应用越来越多时候，应用之间交互不可避免，</li>
<li><strong>将核心业务抽取出来，作为独立的服务，逐渐形成稳定的服务中心</strong>，</li>
<li>使得前端应用能快速的响应多变的市场需求。此时，用于提高业务复用及整合的<strong>分布式框架(RPC)是关键。</strong></li>
</ul>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410110634.png" alt=""></p>
<p>优点：</p>
<ul>
<li>将基础服务进行了抽取，系统间相互调用，提高了代码的复用和开发的效率</li>
</ul>
<p>缺点：</p>
<ul>
<li><strong>系统间的耦合度提高</strong>，关系复杂，难以维护</li>
</ul>
<p><strong>分布式和集群的联系和区别：</strong></p>
<ul>
<li>分布式：一个业务分拆多个子业务，部署在不同的服务器上</li>
<li>集群：同一个业务，部署在多个服务器上</li>
<li>分布式中的每一个节点，都可以当作一个集群来实现</li>
<li><strong>集群有个哨兵，主机宕机了可以有别的服务器顶上来，但是分布式如果有个节点宕机了，那么整个服务都不可用。</strong></li>
<li><strong>好的设计应该是分布式和集群的结合。先进行分布式再集群，具体实现就是把业务拆分成多个子业务，然后针对集群部署，这样每个子业务如果出现了问题，那么整个系统也不会受到影响</strong></li>
</ul>
<h3 id="2-4-流动计算架构-SOA"><a href="#2-4-流动计算架构-SOA" class="headerlink" title="2.4 流动计算架构(SOA)"></a>2.4 流动计算架构(SOA)</h3><ul>
<li>当服务越来愈多，容量的评估，小服务资源的浪费等问题逐渐显现，此时需要增加一个<strong>调度中心（基于访问压力实施管理集群容量，提高集群的利用效率。）</strong></li>
<li>此时，<strong>用于提高机器利用率的资源调度和治理中心(SOA)是关键</strong>（Service-Oriented Architecture）<strong>面向服务的架构</strong></li>
</ul>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410110929.png" alt=""></p>
<p><strong>阿里巴巴内部目前使用的框架：HSF（好舒服），是dubbo的升级版</strong></p>
<p>以前出现了什么问题？</p>
<ul>
<li>服务越来越多，需要管理每个服务的地址</li>
<li>调用关系错综复杂，难以理清依赖关系</li>
<li>服务过多，服务状态难以管理，无法根据服务情况动态管理</li>
</ul>
<p><strong>服务治理要做什么？</strong></p>
<ul>
<li>服务注册中心，实现<strong>服务自动注册和发现</strong>，无需人为记录服务地址</li>
<li><strong>服务自动订阅</strong>，服务列表自动推送，服务调用透明化，无需关心依赖关系。</li>
<li><strong>动态监控服务状态和监控报告</strong>，人为控制服务状态。</li>
</ul>
<p>缺点：</p>
<ul>
<li>服务之间会有依赖关系，一旦某个环节出错影响比较大</li>
<li>服务关系复杂，运维，测试部署困难，不符合DevOps思想</li>
</ul>
<h3 id="2-5-微服务"><a href="#2-5-微服务" class="headerlink" title="2.5 微服务"></a>2.5 微服务</h3><p><img src="http://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200717/210131229.png" alt="mark"></p>
<ul>
<li>前面说的SOA，英文翻译过来是面向服务的编程。</li>
<li>微服务，似乎也是服务，都是对系统进行拆分。因此两者非常容易混淆，但其实却有一些差别：</li>
</ul>
<table>
<thead>
<tr>
<th>功能</th>
<th>SOA</th>
<th>微服务</th>
</tr>
</thead>
<tbody><tr>
<td>组件大小</td>
<td>大块业务逻辑</td>
<td>单独任务或小块业务逻辑</td>
</tr>
<tr>
<td>耦合</td>
<td>通常松耦合</td>
<td>总是松耦合</td>
</tr>
<tr>
<td>公司架构</td>
<td>任何类型</td>
<td>小型、专注于功能交叉团队</td>
</tr>
<tr>
<td>管理</td>
<td><strong>着重中央管理</strong></td>
<td><strong>着重分散管理</strong></td>
</tr>
<tr>
<td>目标</td>
<td>确保应用能够交互操作</td>
<td>执行新功能、快速拓展开发团队</td>
</tr>
</tbody></table>
<p><strong>微服务特点：</strong></p>
<p><strong>1.通过服务实现组件化</strong></p>
<ul>
<li>开发者不再需要协调其它服务部署对本服务的影响。</li>
</ul>
<p><strong>2.按业务能力来划分服务和开发团队</strong></p>
<ul>
<li>开发者可以自由选择开发技术，提供 API 服务</li>
</ul>
<p><strong>3.去中心化</strong></p>
<ul>
<li><p><strong>让一切去中心化是微服务的最高宗旨，</strong></p>
</li>
<li><p>每个微服务有自己私有的数据库持久化业务数据</p>
</li>
<li><p>每个微服务只能访问自己的数据库，而不能访问其它服务的数据库</p>
</li>
<li><p>某些业务场景下，需要在一个事务中更新多个数据库。这种情况也不能直接访问其它微服务的数据库，而是通过对于微服务进行操作。</p>
</li>
<li><p><strong>数据的去中心化，进一步降低了微服务之间的耦合度，不同服务可以采用不同的数据库技术（SQL、NoSQL等）。在复杂的业务场景下，如果包含多个微服务，通常在客户端或者中间层（网关）处理。</strong></p>
</li>
</ul>
<p><strong>4.基础设施自动化（devops、自动化部署）</strong></p>
<ul>
<li>Java EE部署架构，通过展现层打包WAR，业务层划分到JARs最后部署为EAR一个大包，</li>
<li>而微服务则打开了这个黑盒子，把应用拆分成为一个一个的单个服务，应用Docker技术，不依赖任何服务器和数据模型，是一个全栈应用，</li>
<li>可以通过自动化方式独立部署，每个服务运行在自己的进程中，通过<strong>轻量的通讯机制联系（RESTful 或者  异步（消息队列/发布订阅））</strong>，经常是基于HTTP资源API，这些服务基于业务能力构建，能实现集中化管理（因为服务太多啦，不集中管理就无法DevOps啦）。</li>
</ul>
<p><img src="http://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200717/210425647.png" alt="mark"></p>
<p><strong>微服务的优点</strong></p>
<ul>
<li>每个微服务都很小，这样的单个服务很容易开发和维护</li>
<li>微服务<strong>能够被小团队单独开发</strong>，这个小团队是2到5人的开发人员组成</li>
<li><strong>微服务是松耦合的，可以使用不同的语言进行开发</strong></li>
</ul>
<p><strong>这里微服务有篇论文：我的博客里有中文阅读笔记，搜索tags 标签是微服务就可以找到啦！！</strong></p>
<h2 id="3-RPC-远程过程调用"><a href="#3-RPC-远程过程调用" class="headerlink" title="3. RPC(远程过程调用)"></a>3. RPC(远程过程调用)</h2><ul>
<li><strong>remote produce call(RPC)</strong></li>
</ul>
<h3 id="3-1-常见的远程调用方式"><a href="#3-1-常见的远程调用方式" class="headerlink" title="3.1 常见的远程调用方式"></a>3.1 常见的远程调用方式</h3><p>无论是微服务还是SOA，都面临着<strong>服务间的远程调用</strong>。那么服务间的远程调用方式有哪些呢？</p>
<ul>
<li><strong>RPC : remote produce call</strong>      <ul>
<li><strong>可以自定义数据的格式，基于原生的TCP通信，速度快，效率高。</strong></li>
<li><strong>早期的WebService 和 现在热门的dubbo , 都是 RPC的典型</strong></li>
</ul>
</li>
<li><strong>HTTP</strong> : <strong>http其实就是一种网络传输协议，</strong><ul>
<li><strong>基于TCP,规定了数据传输的格式，</strong></li>
<li><strong>现在的客户端浏览器和服务端通信基本都是采用HTTP协议，，也可以用来进行远程服务的调用 ，缺点是消息封装臃肿。</strong></li>
<li><strong>现在热门的是RESTFUL风格，就是通过HTTP协议来实现的。</strong></li>
</ul>
</li>
</ul>
<h3 id="3-2-认识RPC"><a href="#3-2-认识RPC" class="headerlink" title="3.2 认识RPC"></a>3.2 认识RPC</h3><ul>
<li>RPC ： 即 Remote Procedure Call（远程过程调用）</li>
<li>RPC是一个<strong>计算机通信协议</strong>。<strong>该协议允许一台计算机远程调用另外一台计算机的子程序，而程序员并不需要知道这个底层的通信实现。</strong></li>
<li><strong>简单的来说： A计算机提供了一个服务，B计算机可以像调用本地方法一样的调用A的服务。</strong></li>
</ul>
<p>通过上面的概念，我们可以知道，实现RPC主要就是做到两点：</p>
<ul>
<li><p>实现远程调用其他计算机的服务</p>
<ul>
<li><strong>要实现远程调用，肯定要通过网络进行传输。</strong>A提供服务，B程序通过网络将请求的参数传递给A，A本地执行后得到结果，再把得到的结果返回给B。</li>
<li>这里需要关注的是两点：<ul>
<li>现在比较流行的RPC框架，<strong>底层都是采用TCP作为传输协议</strong></li>
<li>数据传输的格式：<strong>两个程序进行通信，必须约定好数据传输的格式</strong>。就好比两个人聊天，要使用同一种语言一样，我们必须定义好请求和响应的格式，<strong>另外要在网络中做好序列化和反序列化的方式。</strong></li>
</ul>
</li>
</ul>
</li>
<li><p>像调用本地服务一样调用远程服务</p>
<ul>
<li>如果仅仅是远程调用，还不算是RPC。因为RPC强调的是过程调用，调用的过程对用户而言是应该是透明的，用户不应该关心调用的细节。</li>
<li><strong>可以像调用本地服务一样调用远程服务。所以RPC一定要对调用的过程进行封装。</strong></li>
</ul>
</li>
</ul>
<p><strong>RPC调用流程图：</strong></p>
<p><img src="http://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200718/213848710.png" alt="mark"></p>
<p>想要了解详细的RPC实现，给大家推荐一篇文章：<a href="https://legacy.gitbook.com/book/huge0612/tour-of-rpc/details" target="_blank" rel="noopener">自己动手实现RPC</a></p>
<h2 id="4-Dubbo环境搭建"><a href="#4-Dubbo环境搭建" class="headerlink" title="4. Dubbo环境搭建"></a>4. Dubbo环境搭建</h2><ul>
<li>Apache Dubbo |ˈdʌbəʊ| 是一款高性能、<strong>轻量级的开源Java RPC框架</strong></li>
<li>提供三大核心功能<ul>
<li><strong>面向接口的远程调用方法</strong></li>
<li><strong>智能容错</strong></li>
<li><strong>负载均衡</strong></li>
<li><strong>服务自动注册和发现</strong></li>
</ul>
</li>
</ul>
<ul>
<li>dubbo官网 <a href="http://dubbo.apache.org/zh-cn/index.html" target="_blank" rel="noopener">http://dubbo.apache.org/zh-cn/index.html</a></li>
</ul>
<h3 id="4-1-Dubbo-基本概念"><a href="#4-1-Dubbo-基本概念" class="headerlink" title="4.1 Dubbo 基本概念"></a>4.1 Dubbo 基本概念</h3><p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410112138.png" alt=""></p>
<ul>
<li><strong>服务提供者</strong>（Provider）：暴露服务的服务提供方，服务提供者在启动时，向注册中心注册自己提供的服务。</li>
<li><strong>服务消费者</strong>（Consumer）：调用远程服务的服务消费方，服务消费者在启动时，向注册中心订阅自己所需的服务，服务消费者，从提供者地址列表中，基于软负载均衡算法，选一台提供者进行调用，如果调用失败，再选另一台调用。 </li>
<li><strong>注册中心</strong>（Registry）：注册中心返回服务提供者地址列表给消费者，如果有变更，注册中心将基于长连接推送变更数据给消费者    <strong>(ZooKeeper)</strong></li>
<li><strong>监控中心</strong>（Monitor）：服务消费者和提供者，在内存中累计调用次数和调用时间，定时每分钟发送一次统计数据到监控中心   <strong>（Dubbo-admin）</strong></li>
</ul>
<p><strong>调用关系说明：</strong></p>
<ul>
<li><p><strong>服务容器负责启动</strong>，加载，运行服务提供者。</p>
</li>
<li><p>服务<strong>提供者</strong>在启动时，向注册中心<strong>注册自己提供的服务。</strong></p>
</li>
<li><p>服务<strong>消费者</strong>在启动时，向注册中心<strong>订阅自己所需的服务。</strong></p>
</li>
<li><p><strong>注册中心</strong>返回服务提供者地址列表给消费者，如果有变更，注册中心将基于长连接推送变更数据给消费者</p>
</li>
<li><p><strong>服务消费者</strong>，从提供者地址列表中，基于<strong>软负载均衡算法</strong>，选一台提供者进行调用，如果调用失败，再选另一台调用</p>
</li>
<li><p>服务消费者和提供者，在内存中累计调用次数和调用时间，定时每分钟发送一次统计数据到<strong>监控中心</strong>。</p>
</li>
</ul>
<h3 id="4-2-Zookeeper-安装"><a href="#4-2-Zookeeper-安装" class="headerlink" title="4.2 Zookeeper 安装"></a>4.2 Zookeeper 安装</h3><ol>
<li><strong>下载zookeeper ：解压zookeeper</strong>  <a href="https://zookeeper.apache.org/releases.html" target="_blank" rel="noopener">https://zookeeper.apache.org/releases.html</a></li>
</ol>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410112557.png" alt=""></p>
<ol start="2">
<li><strong>运行/bin/zkServer.cmd ，初次运行会报错，没有zoo.cfg配置文件；</strong></li>
</ol>
<p>可能遇到问题：<strong>闪退 !</strong></p>
<p>解决方案：编辑zkServer.cmd文件末尾添加pause 。这样运行出错就不会退出，会提示错误信息，方便找到原因。</p>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410112644.png" alt=""></p>
<ol start="3">
<li><strong>修改zoo.cfg配置文件</strong></li>
</ol>
<p>将conf文件夹下面的zoo_sample.cfg复制一份改名为zoo.cfg即可。</p>
<p>注意几个重要位置：</p>
<p><code>dataDir=./  临时数据存储的目录（可写相对路径）</code></p>
<p><code>clientPort=2181  zookeeper的端口号</code></p>
<p>修改完成后再次启动zookeeper</p>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410112809.png" alt=""></p>
<ol start="4">
<li>使用zkCli.cmd测试</li>
</ol>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410112906.png" alt=""></p>
<p>ls /：列出zookeeper根下保存的所有节点</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">[zk: 127.0.0.1:2181(CONNECTED) 0] ls &#x2F;</span><br><span class="line">[dubbo,zookeeper]</span><br><span class="line"></span><br><span class="line">create -e &#x2F;zhuuu 123   创建一个zhuuu节点，值为123</span><br><span class="line">get &#x2F;zhuuu             获取&#x2F;zhuuu节点的值</span><br></pre></td></tr></table></figure>

<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410113210.png" alt=""></p>
<h3 id="4-3-dubbo-admin-安装"><a href="#4-3-dubbo-admin-安装" class="headerlink" title="4.3 dubbo-admin 安装"></a>4.3 dubbo-admin 安装</h3><ul>
<li>dubbo本身并不是一个服务软件。它其实就是一个jar包，<strong>能够帮你的java程序连接到zookeeper</strong>，并利用zookeeper消费、提供服务。</li>
<li>但是为了让用户更好的管理监控众多的dubbo服务，官方提供了一个<strong>可视化的监控程序dubbo-admin</strong>，不过这个监控即使不装也不影响使用。</li>
</ul>
<ol>
<li><strong>下载dubbo-admin</strong></li>
</ol>
<p><a href="https://github.com/apache/dubbo-admin/tree/master" target="_blank" rel="noopener">https://github.com/apache/dubbo-admin/tree/master</a></p>
<ol start="2">
<li><strong>解压进入目录</strong></li>
</ol>
<p>修改 dubbo-admin\src\main\resources \application.properties 指定zookeeper地址</p>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410113512.png" alt=""></p>
<figure class="highlight properties"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">server.port</span>=<span class="string">7001</span></span><br><span class="line"><span class="meta">spring.velocity.cache</span>=<span class="string">false</span></span><br><span class="line"><span class="meta">spring.velocity.charset</span>=<span class="string">UTF-8</span></span><br><span class="line"><span class="meta">spring.velocity.layout-url</span>=<span class="string">/templates/default.vm</span></span><br><span class="line"><span class="meta">spring.messages.fallback-to-system-locale</span>=<span class="string">false</span></span><br><span class="line"><span class="meta">spring.messages.basename</span>=<span class="string">i18n/message</span></span><br><span class="line"><span class="meta">spring.root.password</span>=<span class="string">root</span></span><br><span class="line"><span class="meta">spring.guest.password</span>=<span class="string">guest</span></span><br><span class="line"></span><br><span class="line"><span class="meta">dubbo.registry.address</span>=<span class="string">zookeeper://127.0.0.1:2181</span></span><br></pre></td></tr></table></figure>

<ol start="3">
<li><strong>在项目目录下</strong>打包dubbo-admin</li>
</ol>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">mvn clean package -Dmaven.test.skip&#x3D;true</span><br></pre></td></tr></table></figure>

<p><strong>第一次打包的过程有点慢，需要耐心等待！直到成功！</strong></p>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410113636.png" alt=""></p>
<p><strong>打包完成后会产生一个jar包</strong></p>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410113644.png" alt=""></p>
<ol start="4">
<li><strong>执行 dubbo-admin\target 下的dubbo-admin-0.0.1-SNAPSHOT.jar</strong></li>
</ol>
<figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">java -jar dubbo-admin-0.0.1-SNAPSHOT.jar</span><br></pre></td></tr></table></figure>

<p><strong>【注意：zookeeper的服务一定要打开！】</strong></p>
<p>执行完毕，我们去访问一下 <a href="http://localhost:7001/" target="_blank" rel="noopener">http://localhost:7001/</a> ， 这时候我们需要输入登录账户和密码 默认的root-root；</p>
<p>登录成功后，查看界面</p>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410113945.png" alt=""></p>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410114010.png" alt=""></p>
<h2 id="5-SpringBoot-Dubbo-zookeeper"><a href="#5-SpringBoot-Dubbo-zookeeper" class="headerlink" title="5. SpringBoot + Dubbo + zookeeper"></a>5. SpringBoot + Dubbo + zookeeper</h2><p><strong>测试环境搭建：</strong></p>
<p><strong>1. 启动zookeeper ！</strong></p>
<p><strong>2. IDEA创建一个空项目；</strong></p>
<p><strong>3.创建一个模块，实现服务提供者：provider-server ， 选择web依赖即可</strong></p>
<p><strong>4.项目创建完毕，我们写一个服务，比如卖票的服务；</strong></p>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410142551.png" alt=""></p>
<h3 id="5-1-服务提供者"><a href="#5-1-服务提供者" class="headerlink" title="5.1 服务提供者"></a>5.1 服务提供者</h3><ol>
<li><strong>导入依赖(dubbo + zk)</strong> </li>
</ol>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">&lt;!-- Dubbo Spring Boot Starter --&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.apache.dubbo<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>dubbo-spring-boot-starter<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">version</span>&gt;</span>2.7.3<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br></pre></td></tr></table></figure>

<p><strong>zookeeper的包我们去maven仓库下载，zkclient；</strong></p>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">&lt;!-- https://mvnrepository.com/artifact/com.github.sgroschupf/zkclient --&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>com.github.sgroschupf<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>zkclient<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">version</span>&gt;</span>0.1<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br></pre></td></tr></table></figure>

<p><strong>【新版的坑】zookeeper及其依赖包，解决日志冲突，还需要剔除日志依赖；</strong></p>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">&lt;!-- 引入zookeeper --&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.apache.curator<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>curator-framework<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">version</span>&gt;</span>2.12.0<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.apache.curator<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>curator-recipes<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">version</span>&gt;</span>2.12.0<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.apache.zookeeper<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>zookeeper<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">version</span>&gt;</span>3.4.14<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line">   <span class="comment">&lt;!--排除这个slf4j-log4j12--&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">exclusions</span>&gt;</span></span><br><span class="line">       <span class="tag">&lt;<span class="name">exclusion</span>&gt;</span></span><br><span class="line">           <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.slf4j<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">           <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>slf4j-log4j12<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">       <span class="tag">&lt;/<span class="name">exclusion</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;/<span class="name">exclusions</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br></pre></td></tr></table></figure>

<ol start="2">
<li><strong>编写接口</strong></li>
</ol>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.zhuuu.service;</span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">interface</span> <span class="title">TicketService</span> </span>&#123;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> String <span class="title">getTicket</span><span class="params">()</span></span>;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<ol start="3">
<li><strong>编写实现类</strong></li>
</ol>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.zhuuu.service;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> org.apache.dubbo.config.annotation.Service;</span><br><span class="line"><span class="keyword">import</span> org.springframework.stereotype.Component;</span><br><span class="line"></span><br><span class="line"><span class="comment">// zookeeper: 服务注册与发现</span></span><br><span class="line"><span class="meta">@Service</span> <span class="comment">//将服务发布出去</span></span><br><span class="line"><span class="meta">@Component</span> <span class="comment">//放在容器中</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">TicketServiceImpl</span> <span class="keyword">implements</span> <span class="title">TicketService</span></span>&#123;</span><br><span class="line">    <span class="meta">@Override</span></span><br><span class="line">    <span class="function"><span class="keyword">public</span> String <span class="title">getTicket</span><span class="params">()</span> </span>&#123;</span><br><span class="line">        <span class="keyword">return</span> <span class="string">"朱酱酱的个人学习门票"</span>;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<ol start="4">
<li>在配置文件中配置dubbo相关属性！</li>
</ol>
<figure class="highlight properties"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment"># 当前应用名字</span></span><br><span class="line"><span class="meta">dubbo.application.name</span>=<span class="string">provider-server</span></span><br><span class="line"><span class="comment"># 注册中心地址</span></span><br><span class="line"><span class="meta">dubbo.registry.address</span>=<span class="string">zookeeper://127.0.0.1:2181</span></span><br><span class="line"><span class="comment"># 扫描指定包下服务</span></span><br><span class="line"><span class="meta">dubbo.scan.base-packages</span>=<span class="string">com.kuang.provider.service</span></span><br></pre></td></tr></table></figure>

<p><strong>逻辑理解 ：应用启动起来，dubbo就会扫描指定的包下带有@component注解的服务，将它发布在指定的注册中心中！</strong></p>
<h3 id="5-2-服务消费者"><a href="#5-2-服务消费者" class="headerlink" title="5.2 服务消费者"></a>5.2 服务消费者</h3><ol>
<li><strong>导入依赖，和之前的依赖一样；</strong></li>
</ol>
<figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">&lt;!--dubbo--&gt;</span></span><br><span class="line"><span class="comment">&lt;!-- Dubbo Spring Boot Starter --&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.apache.dubbo<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>dubbo-spring-boot-starter<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">version</span>&gt;</span>2.7.3<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br><span class="line"><span class="comment">&lt;!--zookeeper--&gt;</span></span><br><span class="line"><span class="comment">&lt;!-- https://mvnrepository.com/artifact/com.github.sgroschupf/zkclient --&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>com.github.sgroschupf<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>zkclient<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">version</span>&gt;</span>0.1<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br><span class="line"><span class="comment">&lt;!-- 引入zookeeper --&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.apache.curator<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>curator-framework<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">version</span>&gt;</span>2.12.0<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.apache.curator<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>curator-recipes<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">version</span>&gt;</span>2.12.0<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;<span class="name">dependency</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.apache.zookeeper<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>zookeeper<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">version</span>&gt;</span>3.4.14<span class="tag">&lt;/<span class="name">version</span>&gt;</span></span><br><span class="line">   <span class="comment">&lt;!--排除这个slf4j-log4j12--&gt;</span></span><br><span class="line">   <span class="tag">&lt;<span class="name">exclusions</span>&gt;</span></span><br><span class="line">       <span class="tag">&lt;<span class="name">exclusion</span>&gt;</span></span><br><span class="line">           <span class="tag">&lt;<span class="name">groupId</span>&gt;</span>org.slf4j<span class="tag">&lt;/<span class="name">groupId</span>&gt;</span></span><br><span class="line">           <span class="tag">&lt;<span class="name">artifactId</span>&gt;</span>slf4j-log4j12<span class="tag">&lt;/<span class="name">artifactId</span>&gt;</span></span><br><span class="line">       <span class="tag">&lt;/<span class="name">exclusion</span>&gt;</span></span><br><span class="line">   <span class="tag">&lt;/<span class="name">exclusions</span>&gt;</span></span><br><span class="line"><span class="tag">&lt;/<span class="name">dependency</span>&gt;</span></span><br></pre></td></tr></table></figure>

<ol start="2">
<li><strong>配置参数properties</strong></li>
</ol>
<figure class="highlight properties"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment"># 当前应用名字（暴露自己的名字）</span></span><br><span class="line"><span class="meta">dubbo.application.name</span>=<span class="string">consumer-server</span></span><br><span class="line"><span class="comment"># 注册中心地址(去哪里拿服务)</span></span><br><span class="line"><span class="meta">dubbo.registry.address</span>=<span class="string">zookeeper://127.0.0.1:2181</span></span><br></pre></td></tr></table></figure>

<ol start="3">
<li><strong>本来正常步骤是需要将服务提供者的接口打包，然后用pom文件导入，我们这里使用简单的方式，直接将服务的接口拿过来，路径必须保证正确，即和服务提供者相同；</strong></li>
</ol>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410143253.png" alt=""></p>
<ol start="4">
<li>完善消费者的服务类</li>
</ol>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.zhuuu.service;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> org.apache.dubbo.config.annotation.Reference;</span><br><span class="line"><span class="keyword">import</span> org.springframework.stereotype.Service;</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@Service</span>  <span class="comment">// 与provider不同，这里是放到spring容器中</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">UserService</span> </span>&#123;</span><br><span class="line"></span><br><span class="line">    <span class="comment">// 想拿到票provider-server提供的票,要去注册中心拿到服务</span></span><br><span class="line"></span><br><span class="line">    <span class="meta">@Reference</span>  <span class="comment">// dubbo引用  (pom坐标，定义路径相同的接口名)</span></span><br><span class="line">    TicketService ticketService;</span><br><span class="line"></span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">buyTicket</span><span class="params">()</span></span>&#123;</span><br><span class="line">        String ticket = ticketService.getTicket();</span><br><span class="line">        System.out.println(<span class="string">"在注册中心拿到=》"</span>+ ticket);</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<ol start="5">
<li>测试类编写</li>
</ol>
<figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.zhuuu;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> com.zhuuu.service.UserService;</span><br><span class="line"><span class="keyword">import</span> org.junit.jupiter.api.Test;</span><br><span class="line"><span class="keyword">import</span> org.springframework.beans.factory.annotation.Autowired;</span><br><span class="line"><span class="keyword">import</span> org.springframework.boot.test.context.SpringBootTest;</span><br><span class="line"></span><br><span class="line"><span class="meta">@SpringBootTest</span></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">ConsumerServerApplicationTests</span> </span>&#123;</span><br><span class="line">    <span class="meta">@Autowired</span></span><br><span class="line">    UserService userService;</span><br><span class="line"></span><br><span class="line">    <span class="meta">@Test</span></span><br><span class="line">    <span class="function"><span class="keyword">void</span> <span class="title">contextLoads</span><span class="params">()</span> </span>&#123;</span><br><span class="line">        userService.buyTicket();</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>



<h3 id="5-3-启动测试"><a href="#5-3-启动测试" class="headerlink" title="5.3 启动测试"></a>5.3 启动测试</h3><p><strong>1. 开启zookeeper</strong></p>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410143629.png" alt=""></p>
<p><strong>2. 打开dubbo-admin实现监控【可以不用做】</strong></p>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410143657.png" alt=""><strong>3. 开启服务者</strong></p>
<p><strong>4.开启消费者</strong></p>
<p><img src="https://zhuuu-bucket.oss-cn-beijing.aliyuncs.com/img/20200410143758.png" alt=""></p>

      
      <!-- reward -->
      
      <div id="reward-btn">
        打赏
      </div>
      
    </div>
      <!-- copyright -->
      
        <div class="declare">
          <ul class="post-copyright">
            <li>
              <i class="ri-copyright-line"></i>
              <strong>版权声明： </strong s>
              本博客所有文章除特别声明外，均采用 <a href="https://www.apache.org/licenses/LICENSE-2.0.html" rel="external nofollow"
                target="_blank">Apache License 2.0</a> 许可协议。转载请注明出处！
            </li>
          </ul>
        </div>
        
    <footer class="article-footer">
      
          
<div class="share-btn">
      <span class="share-sns share-outer">
        <i class="ri-share-forward-line"></i>
        分享
      </span>
      <div class="share-wrap">
        <i class="arrow"></i>
        <div class="share-icons">
          
          <a class="weibo share-sns" href="javascript:;" data-type="weibo">
            <i class="ri-weibo-fill"></i>
          </a>
          <a class="weixin share-sns wxFab" href="javascript:;" data-type="weixin">
            <i class="ri-wechat-fill"></i>
          </a>
          <a class="qq share-sns" href="javascript:;" data-type="qq">
            <i class="ri-qq-fill"></i>
          </a>
          <a class="douban share-sns" href="javascript:;" data-type="douban">
            <i class="ri-douban-line"></i>
          </a>
          <!-- <a class="qzone share-sns" href="javascript:;" data-type="qzone">
            <i class="icon icon-qzone"></i>
          </a> -->
          
          <a class="facebook share-sns" href="javascript:;" data-type="facebook">
            <i class="ri-facebook-circle-fill"></i>
          </a>
          <a class="twitter share-sns" href="javascript:;" data-type="twitter">
            <i class="ri-twitter-fill"></i>
          </a>
          <a class="google share-sns" href="javascript:;" data-type="google">
            <i class="ri-google-fill"></i>
          </a>
        </div>
      </div>
</div>

<div class="wx-share-modal">
    <a class="modal-close" href="javascript:;"><i class="ri-close-circle-line"></i></a>
    <p>扫一扫，分享到微信</p>
    <div class="wx-qrcode">
      <img src="//api.qrserver.com/v1/create-qr-code/?size=150x150&data=http://zhuuu.work/2020/04/06/SpringBoot/SpringBoot-18-dubbo+zookeeper/" alt="微信分享二维码">
    </div>
</div>

<div id="share-mask"></div>
      
      
  <ul class="article-tag-list" itemprop="keywords"><li class="article-tag-list-item"><a class="article-tag-list-link" href="/tags/RPC/" rel="tag">RPC</a></li><li class="article-tag-list-item"><a class="article-tag-list-link" href="/tags/SpringBoot/" rel="tag">SpringBoot</a></li><li class="article-tag-list-item"><a class="article-tag-list-link" href="/tags/%E5%88%86%E5%B8%83%E5%BC%8F/" rel="tag">分布式</a></li></ul>


    </footer>

  </div>

  
  
  <nav class="article-nav">
    
      <a href="/2020/04/07/Redis/Redis-02-%E5%85%A5%E9%97%A8%E4%B8%8E%E4%BD%BF%E7%94%A8/" class="article-nav-link">
        <strong class="article-nav-caption">上一篇</strong>
        <div class="article-nav-title">
          
            Redis-02-入门与使用
          
        </div>
      </a>
    
    
      <a href="/2020/04/05/jdk_SourceCode/JDK1.8-05-ArrayList/" class="article-nav-link">
        <strong class="article-nav-caption">下一篇</strong>
        <div class="article-nav-title">JDK1.8源码-05-java.util.ArrayList</div>
      </a>
    
  </nav>


  

  
  
<!-- valine评论 -->
<div id="vcomments-box">
    <div id="vcomments">
    </div>
</div>
<script src="//cdn1.lncld.net/static/js/3.0.4/av-min.js"></script>
<script src='https://cdn.jsdelivr.net/npm/valine@1.3.10/dist/Valine.min.js'></script>
<script>
    new Valine({
        el: '#vcomments',
        notify: false,
        verify: '',
        app_id: '',
        app_key: '',
        path: window.location.pathname,
        avatar: 'mp',
        placeholder: '给我的文章加点评论吧~',
        recordIP: true
    });
    const infoEle = document.querySelector('#vcomments .info');
    if (infoEle && infoEle.childNodes && infoEle.childNodes.length > 0) {
        infoEle.childNodes.forEach(function (item) {
            item.parentNode.removeChild(item);
        });
    }
</script>
<style>
    #vcomments-box {
        padding: 5px 30px;
    }

    @media screen and (max-width: 800px) {
        #vcomments-box {
            padding: 5px 0px;
        }
    }

    #vcomments-box #vcomments {
        background-color: #fff;
    }

    .v .vlist .vcard .vh {
        padding-right: 20px;
    }

    .v .vlist .vcard {
        padding-left: 10px;
    }
</style>

  

  
  
<div class="gitalk" id="gitalk-container"></div>

<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/gitalk@1.5.0/dist/gitalk.css">


<script src="https://cdn.jsdelivr.net/npm/gitalk@1.5.0/dist/gitalk.min.js"></script>


<script src="https://cdn.jsdelivr.net/npm/blueimp-md5@2.10.0/js/md5.min.js"></script>

<script type="text/javascript">
  var gitalk = new Gitalk({
    clientID: 'db188ed8c86dc4b0dbf3',
    clientSecret: 'a58f92160e5a9efd726b7d533000a0737f3e3f3e',
    repo: 'Blog-comments',
    owner: 'Zhuuuuuuuu',
    admin: ['Zhuuuuuuuu'],
    // id: location.pathname,      // Ensure uniqueness and length less than 50
    id: md5(location.pathname),
    distractionFreeMode: false,  // Facebook-like distraction free mode
    pagerDirection: 'last'
  })

  gitalk.render('gitalk-container')
</script>

  

</article>
</section>
      <footer class="footer">
  <div class="outer">
    <ul class="list-inline">
      <li>
        &copy;
        2019-2021
        Zhuuu
      </li>
      <li>
        
      </li>
    </ul>
    <ul class="list-inline">
      <li>
        
        
        <span>
  <i>PV:<span id="busuanzi_value_page_pv"></span></i>
  <i>UV:<span id="busuanzi_value_site_uv"></span></i>
</span>
        
      </li>
      <li>
        <!-- cnzz统计 -->
        
        <script type="text/javascript" src='https://s9.cnzz.com/z_stat.php?id=1278069914&amp;web_id=1278069914'></script>
        
      </li>
    </ul>
  </div>
</footer>
    <div class="to_top">
        <div class="totop" id="totop">
  <i class="ri-arrow-up-line"></i>
</div>
      </div>
    </main>
      <aside class="sidebar">
        <button class="navbar-toggle"></button>
<nav class="navbar">
  
  <div class="logo">
    <a href="/"><img src="/images/ayer-side.svg" alt="朱酱酱的学习博客"></a>
  </div>
  
  <ul class="nav nav-main">
    
    <li class="nav-item">
      <a class="nav-item-link" href="/">主页</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags">标签</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/JVM/">JVM</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/JDK%E6%BA%90%E7%A0%81%E5%88%86%E6%9E%90/">JDK源码</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/%E5%A4%9A%E7%BA%BF%E7%A8%8B/">多线程</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/Mysql/">Mysql</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/Redis/">Redis</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/%E8%AE%BE%E8%AE%A1%E8%80%85%E6%A8%A1%E5%BC%8F/">设计模式</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/MyBatis/">MyBatis</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/SpringMVC/">SpringMVC</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/Spring/">Spring</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/SpringBoot/">SpringBoot</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F/">Linux</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/Leetcode/">Leetcode</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/%E5%89%8D%E7%AB%AF/">前端</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/%E7%BD%91%E7%BB%9C%E7%BC%96%E7%A8%8B/">网络编程</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/tags/photoshop/">photoshop</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="http://smartzhuuu.lofter.com/" target="_blank" rel="noopener">摄影</a>
    </li>
    
    <li class="nav-item">
      <a class="nav-item-link" href="/2020/about">关于我</a>
    </li>
    
  </ul>
</nav>
<nav class="navbar navbar-bottom">
  <ul class="nav">
    <li class="nav-item">
      
      <a class="nav-item-link nav-item-search"  title="Search">
        <i class="ri-search-line"></i>
      </a>
      
      
      <a class="nav-item-link" target="_blank" href="/atom.xml" title="RSS Feed">
        <i class="ri-rss-line"></i>
      </a>
      
    </li>
  </ul>
</nav>
<div class="search-form-wrap">
  <div class="local-search local-search-plugin">
  <input type="search" id="local-search-input" class="local-search-input" placeholder="Search...">
  <div id="local-search-result" class="local-search-result"></div>
</div>
</div>
      </aside>
      <div id="mask"></div>

<!-- #reward -->
<div id="reward">
  <span class="close"><i class="ri-close-line"></i></span>
  <p class="reward-p"><i class="ri-cup-line"></i>请我喝杯咖啡吧~</p>
  <div class="reward-box">
    
    <div class="reward-item">
      <img class="reward-img" src="/images/alipay.jpg">
      <span class="reward-type">支付宝</span>
    </div>
    
    
    <div class="reward-item">
      <img class="reward-img" src="/images/wechat.jpg">
      <span class="reward-type">微信</span>
    </div>
    
  </div>
</div>
      
<script src="/js/jquery-2.0.3.min.js"></script>


<script src="/js/jquery.justifiedGallery.min.js"></script>


<script src="/js/lazyload.min.js"></script>


<script src="/js/busuanzi-2.3.pure.min.js"></script>


<script src="/js/share.js"></script>



<script src="/fancybox/jquery.fancybox.min.js"></script>




<script>
  try {
    var typed = new Typed("#subtitle", {
    strings: ['昨夜西风凋碧树。独上高楼，望尽天涯路','衣带渐宽终不悔，为伊消得人憔悴。','众里寻他千百度。蓦然回首，那人却在，灯火阑珊处。'],
    startDelay: 0,
    typeSpeed: 200,
    loop: true,
    backSpeed: 100,
    showCursor: true
    });
  } catch (err) {
  }
  
</script>




<script src="/js/tocbot.min.js"></script>

<script>
  // Tocbot_v4.7.0  http://tscanlin.github.io/tocbot/
  tocbot.init({
    tocSelector: '.tocbot',
    contentSelector: '.article-entry',
    headingSelector: 'h1, h2, h3, h4, h5, h6',
    hasInnerContainers: true,
    scrollSmooth: true,
    scrollContainer:'main',
    positionFixedSelector: '.tocbot',
    positionFixedClass: 'is-position-fixed',
    fixedSidebarOffset: 'auto',
    onClick: (e) => {
      $('.toc-link').removeClass('is-active-link');
      $(`a[href=${e.target.hash}]`).addClass('is-active-link');
      $(e.target.hash).scrollIntoView();
      return false;
    }
  });
</script>


<script>
  var ayerConfig = {
    mathjax: true
  }
</script>


<script src="/js/ayer.js"></script>


<script src="https://cdn.jsdelivr.net/npm/jquery-modal@0.9.2/jquery.modal.min.js"></script>
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/jquery-modal@0.9.2/jquery.modal.min.css">


<!-- Root element of PhotoSwipe. Must have class pswp. -->
<div class="pswp" tabindex="-1" role="dialog" aria-hidden="true">

    <!-- Background of PhotoSwipe. 
         It's a separate element as animating opacity is faster than rgba(). -->
    <div class="pswp__bg"></div>

    <!-- Slides wrapper with overflow:hidden. -->
    <div class="pswp__scroll-wrap">

        <!-- Container that holds slides. 
            PhotoSwipe keeps only 3 of them in the DOM to save memory.
            Don't modify these 3 pswp__item elements, data is added later on. -->
        <div class="pswp__container">
            <div class="pswp__item"></div>
            <div class="pswp__item"></div>
            <div class="pswp__item"></div>
        </div>

        <!-- Default (PhotoSwipeUI_Default) interface on top of sliding area. Can be changed. -->
        <div class="pswp__ui pswp__ui--hidden">

            <div class="pswp__top-bar">

                <!--  Controls are self-explanatory. Order can be changed. -->

                <div class="pswp__counter"></div>

                <button class="pswp__button pswp__button--close" title="Close (Esc)"></button>

                <button class="pswp__button pswp__button--share" style="display:none" title="Share"></button>

                <button class="pswp__button pswp__button--fs" title="Toggle fullscreen"></button>

                <button class="pswp__button pswp__button--zoom" title="Zoom in/out"></button>

                <!-- Preloader demo http://codepen.io/dimsemenov/pen/yyBWoR -->
                <!-- element will get class pswp__preloader--active when preloader is running -->
                <div class="pswp__preloader">
                    <div class="pswp__preloader__icn">
                        <div class="pswp__preloader__cut">
                            <div class="pswp__preloader__donut"></div>
                        </div>
                    </div>
                </div>
            </div>

            <div class="pswp__share-modal pswp__share-modal--hidden pswp__single-tap">
                <div class="pswp__share-tooltip"></div>
            </div>

            <button class="pswp__button pswp__button--arrow--left" title="Previous (arrow left)">
            </button>

            <button class="pswp__button pswp__button--arrow--right" title="Next (arrow right)">
            </button>

            <div class="pswp__caption">
                <div class="pswp__caption__center"></div>
            </div>

        </div>

    </div>

</div>

<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/photoswipe@4.1.3/dist/photoswipe.min.css">
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/photoswipe@4.1.3/dist/default-skin/default-skin.css">
<script src="https://cdn.jsdelivr.net/npm/photoswipe@4.1.3/dist/photoswipe.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/photoswipe@4.1.3/dist/photoswipe-ui-default.min.js"></script>

<script>
    function viewer_init() {
        let pswpElement = document.querySelectorAll('.pswp')[0];
        let $imgArr = document.querySelectorAll(('.article-entry img:not(.reward-img)'))

        $imgArr.forEach(($em, i) => {
            $em.onclick = () => {
                // slider展开状态
                // todo: 这样不好，后面改成状态
                if (document.querySelector('.left-col.show')) return
                let items = []
                $imgArr.forEach(($em2, i2) => {
                    let img = $em2.getAttribute('data-idx', i2)
                    let src = $em2.getAttribute('data-target') || $em2.getAttribute('src')
                    let title = $em2.getAttribute('alt')
                    // 获得原图尺寸
                    const image = new Image()
                    image.src = src
                    items.push({
                        src: src,
                        w: image.width || $em2.width,
                        h: image.height || $em2.height,
                        title: title
                    })
                })
                var gallery = new PhotoSwipe(pswpElement, PhotoSwipeUI_Default, items, {
                    index: parseInt(i)
                });
                gallery.init()
            }
        })
    }
    viewer_init()
</script>



<script type="text/x-mathjax-config">
  MathJax.Hub.Config({
      tex2jax: {
          inlineMath: [ ['$','$'], ["\\(","\\)"]  ],
          processEscapes: true,
          skipTags: ['script', 'noscript', 'style', 'textarea', 'pre', 'code']
      }
  });

  MathJax.Hub.Queue(function() {
      var all = MathJax.Hub.getAllJax(), i;
      for(i=0; i < all.length; i += 1) {
          all[i].SourceElement().parentNode.className += ' has-jax';
      }
  });
</script>

<script src="https://cdn.jsdelivr.net/npm/mathjax@2.7.6/unpacked/MathJax.js?config=TeX-AMS-MML_HTMLorMML"></script>


<script type="text/javascript" src="https://js.users.51.la/20544303.js"></script>
  </div>
</body>

</html>